﻿using System;
using System.Collections.Generic;
using System.Linq;
using System.Text;
using System.Xml.Linq;

namespace ROrganizer.Client
{
    internal class HashSerializer
    {
        public HashEntry[] Deserialize(XDocument document)
        {
            var query = from element in document.Root.Elements()
                        select HashSerializer.Deserialize(element);

            return query.ToArray();
        }

        public HashEntry Deserialize(XDocument document, string file)
        {
            var query = from element in document.Root.Elements()
                        where element.Element("File").Value == file
                        select HashSerializer.Deserialize(element);

            return query.FirstOrDefault();
        }

        private static HashEntry Deserialize(XElement element)
        {
            return new HashEntry
            {
                File = element.Element("File").Value,
                FileTimestamp = DateTime.Parse(element.Element("FileTimestamp").Value).ToUniversalTime(),
                IsChanged = Boolean.Parse(element.Element("IsChanged").Value),
                Info = new HashInfo
                {
                    Hash = element.Element("Hash").Value,
                    Link = element.Element("Link").Value,
                    LinkTimestamp = String.IsNullOrWhiteSpace(element.Element("LinkTimestamp").Value) ? (DateTime?)null : DateTime.Parse(element.Element("LinkTimestamp").Value).ToUniversalTime(),
                }
            };
        }

        public XDocument Serialize(HashEntry[] entries)
        {
            var query = from entry in entries
                        select HashSerializer.Serialize(entry);

            return new XDocument(new XElement("ROrganizer", query.ToArray()));
        }

        public void Update(XDocument document, params HashEntry[] entries)
        {
            foreach (var entry in entries)
            {
                var element = document.Root.Elements().FirstOrDefault(x => x.Element("File").Value == entry.File);
                var created = HashSerializer.Serialize(entry);

                if (element != null)
                {
                    element.ReplaceWith(created);
                }
                else
                {
                    document.Root.Add(created);
                }
            }
        }

        private static XElement Serialize(HashEntry entry)
        {
            return new XElement("HashEntry",
                        new XElement("File", new XCData(entry.File)),
                        new XElement("FileTimestamp", entry.FileTimestamp),
                        new XElement("IsChanged", entry.IsChanged),
                        new XElement("Hash", entry.Info.Hash),
                        new XElement("Link", entry.Info.Link),
                        new XElement("LinkTimestamp", entry.Info.LinkTimestamp));
        }
    }
}
